package com.xuecheng.content.service.impl;

import cn.hutool.core.util.StrUtil;
import com.xuecheng.commons.constants.CourseConstants;
import com.xuecheng.commons.enums.ErrorCode;
import com.xuecheng.commons.model.dto.TeachplanDto;
import com.xuecheng.commons.model.vo.ResponseResult;
import com.xuecheng.commons.model.vo.TeachplanVo;
import com.xuecheng.commons.utils.BeanHelper;
import com.xuecheng.content.domain.po.CourseBase;
import com.xuecheng.content.domain.po.Teachplan;
import com.xuecheng.content.mapper.TeachplanMapper;
import com.xuecheng.content.service.CourseBaseService;
import com.xuecheng.content.service.TeachplanService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.xuecheng.web.exception.BusinessException;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;

/**
 * <p>
 * 课程计划 服务实现类
 * </p>
 *
 * @author itheima
 * @since 2024-05-03
 */
@Service
public class TeachplanServiceImpl extends ServiceImpl<TeachplanMapper, Teachplan> implements TeachplanService {

    @Autowired
    private TeachplanMapper teachplanMapper;

    /*
    * 查询课程计划
    * */
    @Override
    public ResponseResult<TeachplanVo> treeNodes(Long courseId) {
        //1.查询所有数据
        List<TeachplanVo> list= teachplanMapper.treeNodes(courseId);
        //2.筛选一级大纲
        TeachplanVo one=null;
        for (TeachplanVo vo : list) {
            if(vo.getGrade().equals(1)){
                one=vo;
                break;
            }
        }
        //3.筛选二级目录
        List<TeachplanVo> twoList = new ArrayList<>();
        for (TeachplanVo vo : list) {
            if(vo.getGrade().equals(2)){
                twoList.add(vo);
            }
        }
        //3-1将二级添加到一级中
        one.setTeachPlanTreeNodes(twoList);

        //4.遍历二级,筛选三级小节
        for (TeachplanVo two : twoList) {
            //声明三级集合
            List<TeachplanVo> threeList= new ArrayList<>();
            //遍历总数居
            for (TeachplanVo vo : list) {
                if(vo.getParentid().equals(two.getId())){//三级父id=二级id
                    threeList.add(vo);
                }
            }
            //将三级添加到二级中
            two.setTeachPlanTreeNodes(threeList);
        }
        //5.返回一级大纲
        return ResponseResult.okResult(one);
    }

    @Override
    public ResponseResult<TeachplanVo> treeNodes2(Long courseId) {
        //1.查询所有数据
        List<TeachplanVo> list= teachplanMapper.treeNodes(courseId);
        //2.筛选一级大纲
        TeachplanVo one = list.stream().filter(vo -> vo.getGrade().equals(1)).findFirst().get();
        //3.筛选二级目录
        List<TeachplanVo> twoList = list.stream().filter(vo ->
                vo.getGrade().equals(2)).collect(Collectors.toList());
        //3-1将二级添加到一级中
        one.setTeachPlanTreeNodes(twoList);
        //4.筛选三级小节
        for (TeachplanVo two : twoList) {
            List<TeachplanVo> threeList = list.stream().filter(vo ->
                    vo.getParentid().equals(two.getId())).collect(Collectors.toList());
            //4-1将三级添加到二级中
            two.setTeachPlanTreeNodes(threeList);
        }
        //5.返回一级大纲
        return ResponseResult.okResult(one);
    }
    @Autowired
    private CourseBaseService courseBaseService;

    /*
    * 新增或修改课程计划
    * */
    @Override
    public ResponseResult saveOrUpdateTeachplan(TeachplanDto dto) {
        //1.查询课程数据
        CourseBase courseBase = courseBaseService.getById(dto.getCourseId());
        //2.校验课程状态
        if(StrUtil.equals(courseBase.getAuditStatus(), CourseConstants.AUDIT_PUBLISHED_STATUS)){
            throw new BusinessException(ErrorCode.MEDIABINDERROR);
        }
        //3.dto转entity
        Teachplan teachplan = BeanHelper.copyProperties(dto, Teachplan.class);
        teachplan.setCreateDate(LocalDateTime.now());
        //4.如果为二级目录,手动设置parentid
        if(teachplan.getGrade().equals(2)){
            //4-1查询一级大纲id
            Teachplan one = this.lambdaQuery()
                    .eq(Teachplan::getCourseId, dto.getCourseId())
                    .eq(Teachplan::getGrade, 1).one();
            //4-2一级大纲id,设置到二级目录中
            teachplan.setParentid(one.getId());
        }
        //5.如果为三级小节,设置章节数量
        if(teachplan.getId()==null && teachplan.getGrade().equals(3)){
            //5-1 在原有数量上+1
            courseBase.setPlanNum(courseBase.getPlanNum()+1);
            //5-2更新数据库
            courseBaseService.updateById(courseBase);
        }
        //6.保存或更新课程计划
        this.saveOrUpdate(teachplan);
        //6-1 把课程氪状态改为 未提交
        courseBase.setAuditStatus(CourseConstants.AUDIT_UNPAST_STATUS);
        courseBaseService.updateById(courseBase);
        //7. 返回ok
        return ResponseResult.okResult();
    }

    /*
    * 删除课程计划
    * */
    @Override
    public ResponseResult deleteTeachplan(Long teachplanId) {
        //1.查询课程计划
        Teachplan teachplan = this.getById(teachplanId);
        //2.查询课程信息
        CourseBase courseBase = courseBaseService.getById(teachplan.getCourseId());
        //3.校验课程状态
        if(StrUtil.equals(courseBase.getAuditStatus(),CourseConstants.AUDIT_COMMIT_STATUS) ||
        StrUtil.equals(courseBase.getAuditStatus(),CourseConstants.AUDIT_PASTED_STATUS) ||
        StrUtil.equals(courseBase.getAuditStatus(),CourseConstants.AUDIT_PUBLISHED_STATUS)){
            throw new BusinessException(ErrorCode.MEDIABINDERROR);
        }
        //4.删除课程计划
        if(teachplan.getGrade().equals(2)){//二级删除
            //查询该二级下是否有三级
            Long count = this.lambdaQuery()
                    .eq(Teachplan::getParentid, teachplan.getId()).count();
            //判断如果有不能删除
            if(count>0){
                throw new BusinessException(ErrorCode.DELETEERROR);
            }
            this.removeById(teachplanId);
        }else {//三级删除
            //课程章节数量-1
            courseBase.setPlanNum(courseBase.getPlanNum()-1);
            courseBaseService.updateById(courseBase);
            this.removeById(teachplanId);
        }
        //5.返回od
        return ResponseResult.okResult();
    }
}
